<!--
 @description 省市区选择弹窗
 @fileName index.vue
 @author zengqiongying
 @created 2022/10/30 13:04:30
-->
<template>
  <Popup
    v-model="popShow"
    position="bottom"
    title="选择地区"
    :show-cancel-button="false"
    :show-confirm-button="false"
    @confirm="handleSubmit"
  >
    <div class="select-list">
      <div class="option selected-title">
        <span v-for="(item,i) in selName" :key="i" :class="['tab',{'empty':level===i }]" @click="handleClickTab(i)">
          <span v-if="i<=level || !!(selCode[level])">{{ i === level ? placeholder[i] :item }}</span>
        </span>
      </div>
      <div class="list-scroll">
        <Scroll vertical height="100%">
          <div v-for="(item,i) in list" :key="i" class="option" @click="handleClick(item)">
            <span class="name">{{ item.name }}</span>
            <span class="icon" :class="{'checked':item[fieldKey]===selCode[level]}" />
          </div>
        </Scroll>
      </div>
    </div>
  </Popup>
</template>

<script>
import Popup from '@/components/Popup'
import Scroll from '@/components/Scroll'
import { getProvinces, getAreaList } from '@/apis/dataDict'
export default {
  name: 'PopArea',
  components: { Popup, Scroll },
  props: {
    show: {
      type: Boolean,
      default: false
    },
    value: {
      type: [String, Object],
      default: ''
    }, // 选中的值
    fieldKey: {
      type: String,
      default: 'code'
    } // 地区主键字段键名：code 地区编码 ， id 地区ID
  },
  data() {
    return {
      formData: {
        provinceId: '',
        province: '',
        provinceCode: '',
        cityId: '',
        city: '',
        cityCode: '',
        districtId: '',
        district: '',
        districtCode: '',
        townId: '',
        town: '',
        townCode: ''
      },
      placeholder: ['省份/地区', '城市', '区/县', '街道/镇'],
      level: 0,
      provinceList: [],
      cityList: [],
      countyList: [],
      streetList: []
    }
  },

  computed: {
    popShow: {
      set(val) {
        this.$emit('update:show', val)
      },
      get(val) {
        return this.show
      }
    },
    selName() {
      const { province, city, district, town } = this.formData
      return [province, city, district, town]
    },
    list() {
      if (this.level === 0) {
        return this.provinceList
      } else if (this.level === 1) {
        return this.cityList
      } else if (this.level === 2) {
        return this.countyList
      } else if (this.level === 3) {
        return this.streetList
      }
      return []
    },
    selCode() {
      const { provinceId, provinceCode, cityId, cityCode, districtId, districtCode, townId, townCode } = this.formData
      if (this.fieldKey === 'code') {
        return [provinceCode, cityCode, districtCode, townCode]
      }
      return [provinceId, cityId, districtId, townId]
    }
  },
  watch: {
    value: {
      handler(val) {
        this.initFormData()
      },
      deep: true
    }
  },
  created() {
    this.initFormData()
  },
  methods: {
    async initFormData() {
      await this.initProvinceData()
      this.level = 0
      const tmpObj = {}
      if (this.value && (this.value.provinceCode || this.value.provinceId)) {
        if (this.value.provinceCode || this.value.provinceId) {
          if (this.fieldKey === 'id') {
            if (!this.value.provinceCode) {
              const obj = this.provinceList.find(v => v.id === this.value.provinceId)
              tmpObj.provinceCode = obj.code
            }
          } else {
            if (!this.value.provinceId) {
              const obj = this.provinceList.find(v => v.code === this.value.provinceCode)
              tmpObj.provinceId = obj.id
            }
          }
          await this.getCityData(1, this.value.provinceCode, this.value.provinceId)
          this.level = 1
        }
        if (this.value.cityCode || this.value.cityId) {
          if (this.fieldKey === 'id') {
            if (!this.value.cityCode) {
              const obj = this.cityList.find(v => v.id === this.value.cityId)
              tmpObj.cityCode = obj.code
            }
          } else {
            if (!this.value.cityId) {
              const obj = this.cityList.find(v => v.code === this.value.cityCode)
              tmpObj.cityId = obj.id
            }
          }

          await this.getCityData(2, this.value.cityCode, this.value.cityId)
          this.level = 2
        }
        if (this.value.districtCode || this.value.districtId) {
          if (this.fieldKey === 'id') {
            if (!this.value.districtCode) {
              const obj = this.countyList.find(v => v.id === this.value.districtId)
              tmpObj.districtCode = obj.code
            }
          } else {
            if (!this.value.districtId) {
              const obj = this.countyList.find(v => v.code === this.value.districtCode)
              tmpObj.districtId = obj.id
            }
          }
          await this.getCityData(3, this.value.districtCode, this.value.districtId)
          this.level = 3
        }
        if (this.streetList.length > 0 && (this.value.townId || this.value.townCode)) {
          if (this.fieldKey === 'id') {
            if (!this.value.townCode) {
              const obj = this.streetList.find(v => v.id === this.value.townId)
              tmpObj.townCode = obj.code
            }
          } else {
            if (!this.value.townId) {
              const obj = this.streetList.find(v => v.code === this.value.townCode)
              tmpObj.townId = obj.id
            }
          }
        }
      }
      if (Object.keys(tmpObj).length > 0) {
        this.$emit('input', { ...this.value, ...tmpObj })
      }

      for (const key in this.formData) {
        const value = this.value[key] || (tmpObj[key] || '')
        this.$set(this.formData, key, value)
      }
    },
    // 获取所有省份数据
    async initProvinceData() {
      // 获取省
      await getProvinces().then(res => {
        this.provinceList = res.data || []
      })
    },
    /**
     * 获取市、区、街道数据
     * @param {Number} level  等级：1 市 ， 2 区县 ， 3 街道/镇
     * @param {string} parentCode  省编码
     * @param {string} parentCode  省编码
     * @param {string} parentId  省Id
     * @returns {Array} 市列数据
     */
    async getCityData(level, parentCode, parentId) {
      let pId = parentId || ''
      const listName = ['provinceList', 'cityList', 'countyList', 'streetList']
      let checkCode = false // 当前查询参数是否为Code（若长度为20为id,反之code）
      if (this.fieldKey === 'code') {
        // 关键字为Code，通过code查找id进行子级查询
        checkCode = parentCode.length !== 20
        if (!checkCode) {
          pId = parentCode
        }
      } else {
        // 关键字为id,判断当前参数是否为id
        checkCode = parentId.length !== 20
      }

      if (checkCode) {
        const parentList = this[listName[level - 1]]
        const o = parentList.filter(v => v.code === parentCode)
        pId = o && o.length ? o[0].id : '' // 父级ID
      }

      let resultData = []
      if (pId) {
        await getAreaList(pId).then(res => {
          resultData = res.data || []
        })
      }
      this.$set(this, listName[level], resultData)
    },
    handleClickTab(level) {
      this.level = level
    },
    async handleClick(data) {
      const { name, code, id } = data
      if (this.level === 0) {
        const flag = this.fieldKey === 'code' ? this.formData.provinceCode === code : this.formData.provinceId === id
        if (flag) {
          this.level = 1
          return
        }
        this.clearData(['cityId', 'city', 'cityCode', 'districtId', 'district', 'districtCode', 'townId', 'town', 'townCode'])
        this.formData.province = name
        this.formData.provinceId = id
        this.formData.provinceCode = code
        await this.getCityData(1, code, id)
        this.level = 1
      } else if (this.level === 1) {
        const flag = this.fieldKey === 'code' ? this.formData.cityCode === code : this.formData.cityId === id
        if (flag) {
          this.level = 2
          return
        }
        this.clearData(['districtId', 'district', 'districtCode', 'townId', 'town', 'townCode'])
        this.formData.city = name
        this.formData.cityId = id
        this.formData.cityCode = code
        await this.getCityData(2, code, id)
        this.level = 2
      } else if (this.level === 2) {
        const flag = this.fieldKey === 'code' ? this.formData.districtCode === code : this.formData.districtId === id
        if (flag) {
          if (this.streetList.length > 0) {
            this.level = 3
          }
          return
        }
        this.clearData(['townId', 'town', 'townCode'])
        this.formData.district = name
        this.formData.districtId = id
        this.formData.districtCode = code
        await this.getCityData(3, code, id)
        if (this.streetList.length === 0) {
          this.handleSubmit()
        } else {
          this.level = 3
        }
      } else if (this.level === 3) {
        // if (this.formData.townCode === code) return
        this.formData.town = name
        this.formData.townId = id
        this.formData.townCode = code
        this.handleSubmit()
      }
    },
    clearData(fields) {
      if (fields.length === 0) {
        for (const key in this.formData) {
          this.$set(this.formData, key, '')
        }
      } else {
        fields.forEach(v => {
          this.$set(this.formData, v, '')
        })
      }
    },
    handleSubmit() {
      // this.$emit('input', this.formData)
      const districtFlag = this.fieldKey === 'code' ? this.formData.districtCode === '' : this.formData.districtId === ''
      if (districtFlag) {
        this.$toast('请选择完整地区')
        return
      }
      if (this.streetList.length > 0) {
        const streetFlag = this.fieldKey === 'code' ? this.formData.townCode === '' : this.formData.townId === ''
        if (streetFlag) {
          this.$toast('请选择街道')
          return
        }
      }
      const params = {}
      for (const [k, v] of Object.entries(this.formData)) {
        params[k] = v
      }
      this.$emit('input', params)
      this.$emit('change', params)
      this.popShow = false
    }
  }
}

</script>
<style lang='less' scoped>
.select-list{
  padding:0 16px;
  border-radius: 8px;
  // background: rgba(239, 242, 247, .6);
  overflow: hidden;
  .option{
    height: 55px;
    display: flex;
    justify-content: space-between;
    align-items: center;
    border-bottom: 1px solid rgba(0, 0, 0, 0.1);
    &:last-child{
      border-bottom: 0;
    }
  }
  .name{
    font-size: 16px;
    color: #3C4458;
  }
  .icon{
    width: 20px;
    height: 14px;
    margin-left: 10px;
    &.checked{
      background: url(~@/assets/icon-yes.png);
      background-size: 20px 14px;
    }
  }
}
.selected-title{
  justify-content: flex-start !important;
  font-size: 16px;
  color: #3C4458;
  .tab{
    padding-right: 10px;
    // width: 25%;
    height: 20px;
    box-sizing: border-box;
    display: -webkit-box;
    -webkit-box-orient: vertical;
    overflow: hidden;
    -webkit-line-clamp:1;
    &:last-child{
      padding-right: 0;
    }
  }
  .empty{
    color: #B5B7C4;
  }
}
.list-scroll{
  height: 60vh;
}
</style>
